
The examples in this folder show how a parent process can
control the standard streams (stdin, stdout, stderr) of a
child process so that the child "inherits" the parent's
standard streams. Let us explain what we mean by a child
inheriting its parent's standard streams.

When a child inherits a standard stream from its parent,
the parent and child processes "share" the stream. For
example, if the child inherits its parent's standard
output stream, then the parent and child share that stream.
This means that whatever each process writes to its stdout,
that output gets mixed together in the final destination of
the shared stream. If the shared output stream is to a console
window, then the lines of output from the parent and child will
be combined in the console window, usually in an unpredictable
way. The same will happen if the shared output stream is
connected to a file.

On the other hand, if the child inherits its parent's standard
input stream, then both processes read their stdin from that
one stream. What this means is that whichever process calls
"read()" first, that process gets whatever bytes are in the
current input buffer for the shared stream. But the process that
called "read()" second is then in line to be the next process to
get the next batch of bytes that arrive in the stream's buffer.
If both processes are continuously reading from stdin, then
they will probably end up alternately reading input lines from
whatever is the source of the input stream. Notice that any
specific byte in the input stream can only be "read()" by one
of the two processes.

Here is an illustration of parent and child processes sharing
stdin and stdout.

                   parent
                +------------+
                |            |
           +--->>0         1>>-------+
           |    |            |       |
           |    |          2>>       |
           |    |            |       |
           |    |            |       |
           |    |            |       |
           |    +------------+       |
    stdin--+                         +-----> stdout
           |                         |
           |         child           |
           |       +------------+    |
           |       |            |    |
           +------>>0         1>>----+
                   |            |
                   |          2>>
                   |            |
                   |            |
                   |            |
                   +------------+

It is worth noting that usually, when two processes share a stream,
one of them is not actually using the stream. More often than not,
if a parent creates a child and has the child inherit its standard
streams, the parent will not use those streams while the child is
running. The parent will wait until the child is done (the child
process terminates) before the parent goes back to using its
standard streams.

The best, and most common, example of a parent and child sharing
streams is when we type a command at the cmd.exe (or bash) prompt.
For example, suppose we type the command

C:\>FIND "a"

The cmd.exe shell creates a process from the file "find.exe" (that
file is at C:\Windows\System32\find.exe) and the shell has that
process share stdin and stdout with the shell process. Once find.exe
starts, cmd.exe stops using its copies of stdin and stdout and lets
find.exe use its copies. As you type at the keyboard, find.exe looks
for the letter "a" in stdin and echos to stdout any input line that
contains an "a" (find is really a version of grep). When you type ^Z
at the beginning of a line, find.exe sees an EOF on its copy of stdin,
so it exits. But cmd.exe never sees the EOF (the ^Z). When it notices
that find.exe has terminated, cmd.exe goes back to writing and reading
from stdout and stdin. It issues a new prompt on stdout, and waits to
read a new command on stdin. All in all, a very elegant way for a user
to make one program run other programs.

Now back to Java.

In Java, when a child process is created, its three standard streams
do not connect to anything! This is unlike Unix (or Windows), where a
child process always inherits its parent's standard streams.

So in Java, we have to do something special just to be able to get
anything into or out of the child process. In the previous folder we
examined the case of redirecting the child's standard streams to files.
In this folder, we examine the case of the child inheriting (sharing)
its parent's standard streams.

Using Java 7, we are supposed to be able to have the child inherit its
parent's standard streams, but this does not seem to work on Windows.
It does work on Linux, so it seems that there is a bug in the Windows
version of the Java libraries!
See the file
   Java7_ChildInheritsStdStreams.java.
See also this bug report.
   http://bugs.sun.com/view_bug.do?bug_id=8023130


Using Java 6, we can do the child's inheriting of streams, but only
in a very awkward way. The awkward way forces us to simulate the Unix
notion of a "pipe" connecting two streams together, but we have to
create something more like a "pump" in place of the "pipe". Instead of
the output of one stream seamlessly appearing as input to another
stream (if they were connected by a "pipe") we must force (copy) all
the output from one stream to the input of another stream.

Here is a diagram of what we must create in Java 6. Notice that we
have to give the parent process two new streams, a new output stream
(denoted in the diagram by 3) and a new input stream (denoted in the
diagram by 4).

                         parent
                   +-------------------+
                   |                   |
        stdin----->>0--+          +--1>>------> stdout
                   |   |pump      |    |
                   |   |          |  2>>
                   |   |      pump|    |
              +----<<3-+          +--4<<-----+
              |    |                   |     |
              |    +-------------------+     |
              |                              |
              |                              |
              |           child              |
              |       +--------------+       |
              |       |              |       |
              +------>>0           1>>-------+
                      |              |
                      |            2>>
                      |              |
                      |              |
                      |              |
                      +--------------+

See the following files. Be sure to correlate the code in those
files with the above diagram.
   Java6_ChildInheritsStdStreams_ver1.java
   Java6_ChildInheritsStdStreams_ver2.java
   Java6_ChildInheritsStdStreams_ver3.java